package main {
  import flash.display.*;
  import flash.events.*;
  import fl.events.*;
  import flash.text.*;
  import flash.ui.*;
  import flash.net.*;
  import flash.utils.*;
  import fl.controls.*;
  import main.events.*;
  import caurina.transitions.Tweener;
  
  
  /**
   * Main class of the application
   *
   */
  
  public class Main extends MovieClip {
    var mapContainer:MovieClip;
    var placesList:List;
    var putPlaceButton:SimpleButton;
    var cancelButton:SimpleButton;
    
    private var _data_accessor:DataAccessor;
    private var _put_place_panel:PutPlacePanel;
    private var _edit_place_panel:EditPlacePanel;
    private var _loader: Loader;
    
    private var _current_edit_place:String;
    private var _stage_width: Number;
    private var _stage_height: Number;
    private var _viewer_id:Number;
    private var _user_id:Number;
    
    
    /**
     * Constructor
     *
     */
    public function Main() {
      
      // get stage dimensions
      _stage_width = stage.stageWidth > 0 ? stage.stageWidth : 570;
  	  _stage_height = stage.stageHeight > 0 ? stage.stageHeight : 500;
  	  
  	  // get flash vars
      var params:Object = LoaderInfo(root.loaderInfo).parameters;
      _user_id = (params['user_id']) ? parseInt(params['user_id']) : 0;
      _viewer_id = (params['viewer_id']) ? parseInt(params['viewer_id']) : 6492;
      
      // check whether or not application is run from the user page
      if (_user_id <= 0) {
        mainPanel.visible = false;
        installPanel.x = Math.round(_stage_width/2 - installPanel.width/2);
        installPanel.y = 50;
      } else {
        installPanel.visible = false;
        _data_accessor = new DataAccessor(_viewer_id, _user_id);
        
        mapContainer = mainPanel.mapContainer;
        placesList = mainPanel.placesList;
        putPlaceButton = mainPanel.putPlaceButton;
        cancelButton = mainPanel.cancelButton;
        
        init();
      }
    }
    
    /**
     * Initiates display objects and data accessor
     *
     */
    public function init() {
      // init loader movie clip
      _loader = new Loader();
  	  _loader.visible = false;
      _loader.alpha = 0;
  	  _loader.x = Math.round(_stage_width/2 - _loader.width/2);
  	  _loader.y = Math.round(mapContainer.mapMask.height / 2 - _loader.height/2);
  	  addChild(_loader);
  	  
  	  showLoader(true);
  	  
  	  // handle data accessor init event
      _data_accessor.addEventListener(DataAccessor.INIT, function(e:Event){
        showLoader(false);
        var places:Array = _data_accessor.places;
        for (var i:String in places){
          mainPanel.mapContainer.putPlace(places[i].key, places[i].x, places[i].y, places[i].title);
        }
        refreshList();
      });
    
      // reset map stage dimensions
      mapContainer.resetSize();
    
      // show admin buttons
      if (_viewer_id == _user_id) {
        putPlaceButton.addEventListener(MouseEvent.CLICK, onPutPlaceRelease);
        cancelButton.addEventListener(MouseEvent.CLICK, onCancelRelease);
      } else {
        putPlaceButton.visible = false;
        mapContainer.readOnly = true;
      }
      cancelButton.visible = false;
      cancelButton.alpha = 0;
    
      // handle mouse click event on the mapContainer
      mapContainer.addEventListener(MouseEvent.CLICK, function(e:MouseEvent){
        var key = _data_accessor.getUnusedVar();
        if (!key) {
          trace("no more unused vars");
          return;
        }
        trace("get: "+key);
        Tweener.addTween(_put_place_panel,{_autoAlpha:1, time:0.4});
        mapContainer.setMode(MapContainer.MODE_MODAL_WIN);
        mapContainer.putPlace(key, e.localX, e.localY, "Введите название");
      });
      
      // handle item click event on the places list component
      placesList.addEventListener(ListEvent.ITEM_CLICK, function(e:ListEvent) {
        mapContainer.showPlaceTitle(parseInt(e.item.data));
      });
    
      // init panel for putting a place on the map
      _put_place_panel = new PutPlacePanel();
  	  _put_place_panel.visible = false;
  	  _put_place_panel.alpha = 0;
  	  _put_place_panel.x = Math.round(_stage_width/2 - _put_place_panel.width/2);
  	  _put_place_panel.y = 110;
  	  _put_place_panel.put.addEventListener(MouseEvent.CLICK, function(e){
  	    if (_put_place_panel.txtPlace.text == "") return;
  	    var place:Object = mapContainer.getLastPlace();
  	    mapContainer.setPlaceTitle(place.key, _put_place_panel.txtPlace.text);
  	    place.title = _put_place_panel.txtPlace.text;
  	    _put_place_panel.txtPlace.text = "";
  	    _put_place_panel.alpha = 0;
  	    _put_place_panel.visible = false;
  	    _data_accessor.addPlace(place.x, place.y, place.title);
  	    onCancelRelease();
  	    refreshList()
  	  });
  	  _put_place_panel.cancel.addEventListener(MouseEvent.CLICK, function(e){
  	    mapContainer.removePlace(mapContainer.getLastPlace().key);
  	    _put_place_panel.txtPlace.text = "";
  	    _put_place_panel.alpha = 0;
  	    _put_place_panel.visible = false;
  	    onCancelRelease();
  	  });
  	  addChild(_put_place_panel);
	  
      _put_place_panel.txtPlace.maxChars = 50;
      
      // handle event fired when clicking on the exact place
      mapContainer.addEventListener(MapContainer.CLICK_ON_PLACE, function(e:MapEvent) {
        mapContainer.setMode(MapContainer.MODE_MODAL_WIN);
        _current_edit_place = e.placeKey;
        _edit_place_panel.txtPlace.text = mapContainer.getPlace(e.placeKey).title;
        Tweener.addTween(_edit_place_panel, {time:0.5, _autoAlpha:1});
      });
      
      // init edit place panel
      _edit_place_panel = new EditPlacePanel();
  	  _edit_place_panel.visible = false;
  	  _edit_place_panel.alpha = 0;
  	  _edit_place_panel.x = Math.round(_stage_width/2 - _edit_place_panel.width/2);
  	  _edit_place_panel.y = 110;
  	  
  	  _edit_place_panel.save.addEventListener(MouseEvent.CLICK, function(e){
  	    mapContainer.setPlaceTitle(_current_edit_place, _edit_place_panel.txtPlace.text);
  	    var place:Object = mapContainer.getPlace(_current_edit_place);
  	    _data_accessor.editPlace(place.key, place.x, place.y, place.title);
  	    _current_edit_place = "";
  	    _edit_place_panel.txtPlace.text = "";
  	    _edit_place_panel.txtPlace.text = "";
  	    _edit_place_panel.alpha = 0;
  	    _edit_place_panel.visible = false;
  	    refreshList();
  	    onCancelRelease();
  	  });
  	  
  	  _edit_place_panel.remove.addEventListener(MouseEvent.CLICK, function(e){
  	    var place:Object = mapContainer.getPlace(_current_edit_place);
  	    mapContainer.removePlace(place.key);
  	    _data_accessor.removePlace(place.key);
  	    _current_edit_place = "";
  	    _edit_place_panel.txtPlace.text = "";
  	    _edit_place_panel.alpha = 0;
  	    _edit_place_panel.visible = false;
  	    refreshList();
  	    onCancelRelease();
  	  });
  	  
  	  _edit_place_panel.cancel.addEventListener(MouseEvent.CLICK, function(e){
  	    _current_edit_place = "";
  	    _edit_place_panel.txtPlace.text = "";
  	    _edit_place_panel.alpha = 0;
  	    _edit_place_panel.visible = false;
  	    onCancelRelease();
  	  });
  	  addChild(_edit_place_panel);
	  
      _edit_place_panel.txtPlace.maxChars = 50;
      
	    // set styles for text input components
  	  var tf:TextFormat = new TextFormat();
      tf.font = 'Tahoma,Helvetica,Arial,sans-serif';
      tf.size = 12;
      tf.color = 0x0B333C;
      _put_place_panel.txtPlace.setStyle("textFormat", tf);
      _put_place_panel.txtPlace.setStyle("textPadding", 1);
      _edit_place_panel.txtPlace.setStyle("textFormat", tf);
      _edit_place_panel.txtPlace.setStyle("textPadding", 1);
    }
    
    
    /**
     * Event hanlder on putPlace button release
     *
     */
    public function onPutPlaceRelease(e:MouseEvent = null) {
      mapContainer.setMode(MapContainer.MODE_PUT_PLACE);
      Tweener.addTween(putPlaceButton, {time:0.5, _autoAlpha:0});
      Tweener.addTween(cancelButton, {time:0.5, _autoAlpha:1});
    }
    
    /**
     * Event hanlder on cancel button release
     *
     */
    public function onCancelRelease(e:MouseEvent = null) {
      mapContainer.setMode(MapContainer.MODE_DRAG_MAP);
      Tweener.addTween(putPlaceButton, {time:0.5, _autoAlpha:1});
      Tweener.addTween(cancelButton, {time:0.5, _autoAlpha:0});
    }
    
    /**
     * Refreshes data in the list of places component
     *
     */
    public function refreshList(){
      placesList.removeAll();
      var places = mapContainer.getAllPlaces();
      for (var i:String in places) {
        placesList.addItem({label: places[i].title, data: places[i].key});
      }
  	  placesList.sortItemsOn("label");
    }
    
    /**
     * Shows or hides the loader animation
     *
     */
    public function showLoader(show: Boolean = true) {
      if (show) {
        Tweener.addTween(_loader,{_autoAlpha:1, time:0.5})
      } else if (!show) {
        Tweener.addTween(_loader,{_autoAlpha:0, time:0.5})
      }
    }
  }
}